#include <iostream>

#include "helper/helper.h"
#include "helper/mpi_helper.h"

#include "pegasos.h"

int main(int argc, char* argv[]) 
{
  mpi::environment env(argc, argv);
  mpi::communicator world;
  po::variables_map vm;
  Pegasos job(world, vm);

  posix::ptime startTime = CLOCK;
  job.processParameter(argc, argv);
  job.run();
  posix::time_duration duration = CLOCK - startTime;
  MSG("d=" << SECONDS(duration));
  return 0;
}

void Pegasos::processParameter(int argc, char* argv[]) 
{
  desc.add_options()
    ("help", "produce help message")
    ("job,j", po::value<string>(), "job type:\n"
     "  train  : Train a linear SVM\n"
     "  predict: Test a linear SVM"
     )
    // pegasos param
    ("lambda", po::value<double>()->default_value(0.01), "regularization parameter")
    ("sample,k", po::value<int>()->default_value(10), "sampling size")
    ("epoch,e", po::value<double>()->default_value(1), "max epoch")
    // data
    ("input,i", po::value<string>(), "input file")
    ("model,m", po::value<string>()->default_value("default_model"), "model file")
    ("output,o", po::value<string>()->default_value("default_output"), "output file")
    ("verbose,v", po::value<int>()->default_value(1), "0:no info\n1:a little\n2:all")
    ("report,r", po::value<int>()->default_value(100), "number of reports")
    ;
  po::store(po::parse_command_line(argc, argv, desc), vm);
  po::notify(vm);

  if (vm.count("help") || !vm.count("job")) {
    if (MPI_RANK == 0) MSG(desc);
    exit(0);
  }
}

void Pegasos::run() 
{
  REQUIRE_PARAM("job");
  string job = vm["job"].as<string>();
  if (job == "train")
    doTrain();
  else if (job == "predict") 
    doTest();
  else if (job == "cross-validation" || job == "cv")
    doCrossValidation();
  else 
    MSG(desc);
}

